package com.ruoyi.social.service.impl;

import java.util.*;
import java.util.stream.Collectors;

import com.alibaba.fastjson2.JSONArray;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.Apps.Utils.AppUtils;
import com.ruoyi.Apps.Utils.SystemPointConfig;
import com.ruoyi.common.exception.I18nException;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.points.domain.VideoPoints;
import com.ruoyi.points.service.IVideoPointsService;
import com.ruoyi.social.domain.SocialKol;
import com.ruoyi.social.domain.SocialProduct;
import com.ruoyi.video.Enum.AnalysisStatusEnum;
import com.ruoyi.video.Enum.VideoPlatformEnum;
import com.ruoyi.video.domain.VideoAnalysisUser;
import com.ruoyi.video.domain.VideoImages;
import com.ruoyi.video.domain.VideoLineItem;
import com.ruoyi.video.service.IVideoAnalysisUserService;
import com.ruoyi.video.service.IVideoImagesService;
import com.ruoyi.video.service.IVideoLineItemService;
import com.ruoyi.video.service.VideoProcessorService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.ruoyi.social.mapper.SocialVideoMapper;
import com.ruoyi.social.domain.SocialVideo;
import com.ruoyi.social.service.ISocialVideoService;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

/**
 * 视频数据Service业务层处理
 * 
 * @author ruoyi
 * @date 2025-09-24
 */
@Service
public class SocialVideoServiceImpl implements ISocialVideoService 
{
    @Autowired
    private SocialVideoMapper socialVideoMapper;

    @Autowired
    private IVideoAnalysisUserService videoAnalysisUserService;

    @Autowired
    private IVideoImagesService imagesService;

    @Autowired
    private IVideoLineItemService lineItemService;

    @Autowired
    private IVideoPointsService pointsService;

    @Autowired
    private VideoProcessorService processVideo;

    private static final Logger log = LoggerFactory.getLogger(SocialVideoServiceImpl.class);

    /**
     * 查询视频数据
     * 
     * @param id 视频数据主键
     * @return 视频数据
     */
    @Override
    public SocialVideo selectSocialVideoById(Long id)
    {
        return socialVideoMapper.selectSocialVideoById(id);
    }

    /**
     * 查询视频数据列表
     * 
     * @param socialVideo 视频数据
     * @return 视频数据
     */
    @Override
    public List<SocialVideo> selectSocialVideoList(SocialVideo socialVideo)
    {
        return socialVideoMapper.selectSocialVideoList(socialVideo);
    }

    @Override
    public List<SocialVideo> selectSocialVideoListByUserId(Long userId, SocialVideo socialVideo) {
        return socialVideoMapper.selectSocialVideoListByUserId(userId, socialVideo);
    }

    @Override
    @Transactional
    public int updateVideoList(Long userId, List<SocialVideo> videoList, SocialProduct product) {
        if (CollectionUtils.isEmpty(videoList)) {
            return 0;
        }
        videoList = videoList.stream()
                .filter(Objects::nonNull)
                .collect(Collectors.collectingAndThen(
                        Collectors.toCollection(() ->
                                new TreeSet<>(Comparator.comparing(SocialVideo::getVideoOutid))
                        ),
                        ArrayList::new
                ));

        // 1. 批量查询已存在的视频
        List<String> videoOutIds = videoList.stream()
                .map(SocialVideo::getVideoOutid)
                .collect(Collectors.toList());
        List<SocialVideo> existingVideos = socialVideoMapper.selectSocialVideosByOutIds(videoOutIds);
        Map<String, Long> outIdToIdMap = existingVideos.stream()
                .collect(Collectors.toMap(SocialVideo::getVideoOutid, SocialVideo::getId));
        Map<Long, SocialVideo> videoMap = existingVideos.stream()
                .collect(Collectors.toMap(SocialVideo::getId, video -> video));
        // 2. 分离更新和插入的数据
        List<SocialVideo> toUpdate = new ArrayList<>();
        List<SocialVideo> toInsert = new ArrayList<>();

        for (SocialVideo video : videoList) {
            video.setProductId(product.getId());
            Long existingId = outIdToIdMap.get(video.getVideoOutid());

            if (existingId != null) {
                video.setId(existingId);
                SocialVideo old = videoMap.get(existingId);
                video.setVideoNo(old.getVideoNo());
                video.setContent(old.getContent());
                video.setNotes(old.getNotes());
                video.setMp3Path(old.getMp3Path());
                video.setMp4Path(old.getMp4Path());
                video.setVideoTime(old.getVideoTime());
                video.setLanguage(old.getLanguage());
                if(StringUtils.isEmpty(video.getVideoNo())){
                    video.setVideoNo(AppUtils.getSystemTimeId(userId));
                }
                toUpdate.add(video);
            } else {
                video.setVideoNo(AppUtils.getSystemTimeId(userId));
                toInsert.add(video);
            }
        }

        // 3. 批量操作
        int updateCount = 0;
        int insertCount = 0;

        if (!toUpdate.isEmpty()) {
            for (SocialVideo video: toUpdate) {
                updateCount += updateSocialVideo(video);
            }
        }

        if (!toInsert.isEmpty()) {
            insertCount = socialVideoMapper.batchInsertSocialVideo(toInsert);
        }

        // 更新用户关联视频
        List<Long> ids = socialVideoMapper.getIdListByOutIds(videoOutIds);
        videoAnalysisUserService.batchUpdateVideoAnalysisUser(userId, ids);

        return updateCount + insertCount;
    }

    @Override
    public SocialVideo selectFullVideoAnalysisById(Long userId, Long id) {
        SocialVideo videoAnalysis = selectSocialVideoById(id);
        if (StringUtils.isNotNull(videoAnalysis)) {
            VideoAnalysisUser videoAnalysisUser = videoAnalysisUserService.selectVideoAnalysisUserById(userId, id);
            if (StringUtils.isNull(videoAnalysisUser)) {
                return new SocialVideo();
            }
            String status = videoAnalysisUser.getStatus();
            VideoAnalysisUser showUser = new VideoAnalysisUser();
            showUser.setTranslateLanguage(videoAnalysisUser.getTranslateLanguage());
            videoAnalysis.setUser(showUser);
            if (StringUtils.isNotNull(videoAnalysis) &&
                    (Objects.equals(status, AnalysisStatusEnum.END.toString()) || Objects.equals(status, AnalysisStatusEnum.EXTRACT.toString()))) {
                VideoImages search = new VideoImages();
                search.setVideoId(id);
                videoAnalysis.setVideoImages(imagesService.selectVideoImagesList(search));

                VideoLineItem search2 = new VideoLineItem();
                search2.setVideoId(id);
                search2.setUserId(userId);
                List<VideoLineItem> lineItems = lineItemService.selectVideoLineItemList(search2);
                if (!lineItems.isEmpty()) {
                    lineItems.forEach(item->{item.setUserId(null); item.setVideoId(null);});
                }
                videoAnalysis.setVideoLineItems(lineItems);
            }
        }

        return videoAnalysis;
    }

    /**
     * 同步解析数据
     * @param jsonObject
     * @return
     */
    @Override
    public int aiChangeStatus(JSONObject jsonObject) {
        if (StringUtils.isNull( jsonObject )) {
            throw new I18nException("video.sync.errtype");
        }
        String status = jsonObject.getString( "status" );
        JSONObject data = jsonObject.getJSONObject( "data" );
        Long videoId = data.getLong( "video_id" );
        Long userId = data.getLong( "user_id" );
        if (StringUtils.isNull( userId ) || StringUtils.isNull( videoId )) {
            throw new I18nException("video.error.no");
        }
        SocialVideo video = selectSocialVideoById( videoId );
        if (StringUtils.isNull( video )) {
            throw new I18nException("video.error.no");
        }
        VideoAnalysisUser videoAnalysisUser = videoAnalysisUserService.selectVideoAnalysisUserById(userId, videoId);
        if (StringUtils.isNull( videoAnalysisUser )) {
            throw new I18nException("video.error.no");
        }
        if (Objects.equals(status, AnalysisStatusEnum.DOWNLOAD.toString())) {
            // 下载完成
            videoAnalysisUser.setStatus( status );
            String video_path = data.getString( "video_path" );
            String video_time = data.getString( "video_time" );
            video.setVideoTime(Long.parseLong(video_time));
            if (StringUtils.isNotEmpty(video_path)) {
                video.setMp4Path( AppUtils.filterFilePath(video_path) );
            }

            updateSocialVideo( video );
            videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);
        }  else if (Objects.equals(status, AnalysisStatusEnum.DOWNLOADING.toString())) {
            // python 开始下载
            videoAnalysisUser.setStatus( status );
            videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);
        } else if (Objects.equals(status, AnalysisStatusEnum.EXTRACT.toString())) {
            // python 数据准备中
            videoAnalysisUser.setStatus( status );
            String mp3_path = data.getString( "mp3" );
            List<JSONObject> list = data.getList("frames", JSONObject.class);
            video.setMp3Path( AppUtils.filterFilePath(mp3_path) );
            updateSocialVideo( video );
            imagesService.resetImage(videoId, list);
            videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);
        } else if (Objects.equals(status, AnalysisStatusEnum.END.toString())) {
            // AI解析完成
            VideoPoints points = pointsService.selectVideoPointsByUserId(userId);
            videoAnalysisUser.setStatus( status );
            String content = data.getString( "ai_data" );
            video.setContent( content );
            video.setWorkTime( new Date() );
            String content2= AppUtils.extractJsonFromStringV2(content);
            if(StringUtils.isNotEmpty(content2)) {
                JSONObject contentJson = JSONObject.parseObject(content2);
                String source_language = contentJson.getString("source_language");
                if (StringUtils.isNotEmpty(source_language)) {
                    video.setLanguage(source_language);
                }
                JSONArray line = contentJson.getJSONArray("transcriptions");
                if (!line.isEmpty()) {
                    lineItemService.resetVideoLine(userId, videoId, line);
                }
            }

            // 变更积分
            pointsService.changPoint(points, 0 - SystemPointConfig.ACTION_POINT, "AI_Use:"+video.getId());

            updateSocialVideo( video );
            videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);

            // 异步调用
            startNewData();
        } else if (Objects.equals(status, AnalysisStatusEnum.ERROR.toString())) {
            // 操作异常
            videoAnalysisUser.setStatus( status );
            String errormsg = data.getString( "errormsg" );
            videoAnalysisUser.setErrorMsg( errormsg );
            videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);
            // 异步调用
            startNewData();
        } else {
            throw new ServiceException("无效的数据状态!");
        }
        return 1;
    }


    // 请求一条新数据
    void startNewData() {
        VideoAnalysisUser videoAnalysisUser = new VideoAnalysisUser();
//        search.setCreateBy();
        videoAnalysisUser.setStatus(AnalysisStatusEnum.START.toString());
        List<VideoAnalysisUser> list = videoAnalysisUserService.selectVideoAnalysisUserList(videoAnalysisUser);
        if (!list.isEmpty()) {
            try {
                VideoAnalysisUser user = list.get(list.size()-1);
                SocialVideo video = selectSocialVideoById(user.getVideoId());
                processVideo.processVideo(user.getUserId(), video.getId(), video.getVideoLink(),"language="+user.getTranslateLanguage());
            } catch (Exception e) {
            }
        }
    }
    /**
     * 新增视频数据
     * 
     * @param socialVideo 视频数据
     * @return 结果
     */
    @Override
    public int insertSocialVideo(SocialVideo socialVideo)
    {
        return socialVideoMapper.insertSocialVideo(socialVideo);
    }

    @Override
    public int addAnalysisSocialVideo(SocialVideo videoAnalysis) {
        String language = videoAnalysis.getLanguage();
        language = StringUtils.isNotEmpty(language) ? language : "Chinese";
        Long userId = SecurityUtils.getUserId();
        VideoPoints points = pointsService.selectVideoPointsByUserId(userId);
        if (points.getPoints() < SystemPointConfig.ACTION_POINT) {
            throw new I18nException("point.insufficient");
        }
        String url = videoAnalysis.getVideoLink();
        SocialVideo insert = socialVideoMapper.selectSocialVideoByUrl(url);
        int i = 0;
        if(StringUtils.isNull(insert)) {
            // 如果视频地址不存在则新增
            insert = new SocialVideo();
            insert.setVideoLink(videoAnalysis.getVideoLink());
            insert.setCreateTime(new Date());
            insert.setVideoNo(AppUtils.getSystemTimeId());
            insert.setPostPlatform(VideoPlatformEnum.fromUrl(url).toString());
            i = insertSocialVideo(insert);
            // 发送解析
            processVideoForUser(userId, insert.getId(), url, language );
        } else {
            // 视频已经存在
            VideoLineItem search = new VideoLineItem();
            search.setUserId(userId);
            search.setVideoId(insert.getId());
            // 如果已经存用户关联则直接返回
            List<VideoLineItem> items = lineItemService.selectVideoLineItemList(search);
            if (items.isEmpty()) {
                // 如果存在（相同的视频ID和语言）直接复制已经有了的
                items = lineItemService.selectVideoLineItemListGroupByList(insert.getId(), language);
                if (items.isEmpty()) {
                    // 如果没有则继续发送解析
                    String mp3Url = insert.getMp3Path();
                    String reUrl = StringUtils.isNotEmpty(mp3Url)?mp3Url: url;
                    processVideoForUser(userId, insert.getId(), reUrl, language );
                }
            }
        }
        return i;
    }

    @Override
    public void reAnalysisSocialVideo(Long videoId) {
        SocialVideo videoAnalysis = selectSocialVideoById(videoId);
        if(StringUtils.isNull(videoAnalysis)) {
            throw new I18nException("video.error.no");
        }
        Long userId = SecurityUtils.getUserId();
        VideoAnalysisUser videoAnalysisUser = videoAnalysisUserService.selectVideoAnalysisUserById(userId, videoId);
        // 兼容处理 一般不会
        if (StringUtils.isNull(videoAnalysisUser)) {
            throw new I18nException("video.error.no");
        }
        videoAnalysisUser.setStatus(AnalysisStatusEnum.START.toString());
        videoAnalysisUserService.updateVideoAnalysisUser(videoAnalysisUser);
        String mp3Url = videoAnalysis.getMp3Path();
        String reUrl = StringUtils.isNotEmpty(mp3Url)?mp3Url: videoAnalysis.getVideoLink();
        processVideoForUser(userId, videoId, reUrl, videoAnalysisUser.getTranslateLanguage() );
    }

    private void processVideoForUser(Long userId, Long videoId, String url, String language) {
        try {
            if (url.startsWith("/profile/upload/mp4")) {
                url = url.replace("/profile/upload/mp4", "");
            }
            System.out.println("-请求开始-userId:"+userId +" -videoId" + videoId);
//            processVideo.processVideo( userId, videoId, url, "language="+language );
            System.out.println("--返回");
            VideoAnalysisUser analysisUser = videoAnalysisUserService.selectVideoAnalysisUserById(userId, videoId);
            System.out.println("--请求用户关联");
            if (StringUtils.isNull(analysisUser)){
                System.out.println("--管理用户薪资");
                analysisUser = new VideoAnalysisUser();
                analysisUser.setUserId(userId);
                analysisUser.setVideoId(videoId);
                analysisUser.setTranslateLanguage(language);
                analysisUser.setStatus(AnalysisStatusEnum.START.toString());
                videoAnalysisUserService.insertVideoAnalysisUser(analysisUser);
                System.out.println("--结束-----");
            }

        } catch (Exception e) {
            log.error("视频处理失败: videoId={}, url={}", videoId, url, e);
            e.printStackTrace();
            throw new I18nException("video.process.failed");
        }
    }

    /**
     * 修改视频数据
     * 
     * @param socialVideo 视频数据
     * @return 结果
     */
    @Override
    public int updateSocialVideo(SocialVideo socialVideo)
    {
        return socialVideoMapper.updateSocialVideo(socialVideo);
    }

    /**
     * 批量删除视频数据
     * 
     * @param ids 需要删除的视频数据主键
     * @return 结果
     */
    @Override
    public int deleteSocialVideoByIds(Long[] ids)
    {
        return socialVideoMapper.deleteSocialVideoByIds(ids);
    }

    /**
     * 删除视频数据信息
     * 
     * @param id 视频数据主键
     * @return 结果
     */
    @Override
    public int deleteSocialVideoById(Long id)
    {
        return socialVideoMapper.deleteSocialVideoById(id);
    }
}
